package com.kfpanda.search.quartz.job;

import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.quartz.DisallowConcurrentExecution;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.quartz.PersistJobDataAfterExecution;
import org.springframework.batch.core.Job;
import org.springframework.batch.core.JobExecution;
import org.springframework.batch.core.JobParameters;
import org.springframework.batch.core.JobParametersBuilder;
import org.springframework.batch.core.JobParametersInvalidException;
import org.springframework.batch.core.launch.JobLauncher;
import org.springframework.batch.core.repository.JobExecutionAlreadyRunningException;
import org.springframework.batch.core.repository.JobInstanceAlreadyCompleteException;
import org.springframework.batch.core.repository.JobRepository;
import org.springframework.batch.core.repository.JobRestartException;

import com.kfpanda.spring.batch.incrementer.Incrementer;
import com.kfpanda.spring.batch.incrementer.mongo.IncrementerMongodb;

@PersistJobDataAfterExecution
@DisallowConcurrentExecution
public class BatchJobDetail implements org.quartz.Job {
	private static final Log logger = LogFactory.getLog(BatchJobDetail.class);
	
	private JobLauncher jobLauncher;
	private JobRepository jobRepository;
	private Job job;
	private JobParameters jobParameters;
	
	public static final String FAVORITE_COLOR = "favorite color";  
    public static final String EXECUTION_COUNT = "count";  
	@Override
	public void execute(JobExecutionContext context)
			throws JobExecutionException {
		/*JobKey jobKey = context.getJobDetail().getKey();          
        
        JobDataMap data = context.getJobDetail().getJobDataMap();  
        String favoriteColor = data.getString(FAVORITE_COLOR);  
        int count = 0;
        if(flag > 2){count = data.getInt(EXECUTION_COUNT);}
          
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");          
          
        System.out.println("任务Key: " + jobKey + " ,执行时间:  " + sdf.format(new Date()) + "\n" +  
            "  传递参数(favorite color): " + favoriteColor + "\n" +   
            "  传递参数(count):  " + count + "\n" +   
            "  ColorJob静态变量值: " + flag);  
       
        count++;  
        data.put(EXECUTION_COUNT, count);          
        
        flag++; 
        try {
			Thread.sleep(20000);
		} catch (InterruptedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}*/
		this.initJobParams(context);
		
		this.jobRun();
		
	}
	
	
	@SuppressWarnings("unchecked")
	public void initJobParams(JobExecutionContext context){
		this.job = (Job)context.getMergedJobDataMap().get("jobName");
		this.jobLauncher = (JobLauncher)context.getMergedJobDataMap().get("jobLauncher");
		this.jobRepository = (JobRepository)context.getMergedJobDataMap().get("jobRepository");
		JobParametersBuilder paramBuilder = new JobParametersBuilder();
		
		Map<String, String> incremMap = (Map<String, String>)context
				.getMergedJobDataMap().get(IncrementerMongodb.INCREMENTER_NAME);
		//获得自增量，参数。
		if(incremMap != null){
			for( Iterator<Entry<String, String>> itr = incremMap.entrySet().iterator(); 
	    			itr.hasNext(); ){
				Entry<String, String> entry = itr.next();
				paramBuilder.addString( IncrementerMongodb.INCREMENTER_PREX
						+ entry.getKey(), entry.getValue() );
			}
		}
		Map<String, String> paramMap = (Map<String, String>)context.getMergedJobDataMap().get("jobParameters");
		if(paramMap != null){
			for( Iterator<Entry<String, String>> itr = paramMap.entrySet().iterator(); 
	    			itr.hasNext(); ){
				Entry<String, String> entry = itr.next();
				paramBuilder.addString( entry.getKey(), entry.getValue() );
			}
		}
		this.jobParameters = paramBuilder.toJobParameters();
		
	}
	
	public synchronized void jobRun(){
		JobParameters jParam = ( this.jobParameters == null )
				? new JobParameters() : this.jobParameters;
		JobParameters jobParam = ( job.getJobParametersIncrementer() == null ) 
				? jParam : job.getJobParametersIncrementer().getNext(jParam);
		
		try {
			job.getJobParametersValidator().validate(jobParam);
		} catch (JobParametersInvalidException e1) {
			logger.debug(e1);
			return ;
		}
		JobParametersBuilder paramBuilder = new JobParametersBuilder(jobParam);
		paramBuilder.addString(Incrementer.INCREMENTER_NAME, "0");
		jParam = new JobParametersBuilder(jobParam).addString(
				Incrementer.INCREMENTER_NAME, "0").toJobParameters();
		jobParam = new JobParametersBuilder(jobParam).addString(
				Incrementer.BEFORE_INCREMENTER_NAME, "0").toJobParameters();
		//使用jParam作为判断 有无job， jParam中存放 incrementer是 beforeIncrementer的值。
		JobExecution jobExecution = this.jobRepository.getLastJobExecution(job.getName(), jParam);
		if( jobExecution == null || !jobExecution.isRunning() ){
			try {
				jobLauncher.run(job, jobParam);
			} catch (JobExecutionAlreadyRunningException e) {
				logger.error(e);
			} catch (JobRestartException e) {
				logger.error(e);
			} catch (JobInstanceAlreadyCompleteException e) {
				logger.error(e);
			} catch (JobParametersInvalidException e) {
				logger.error(e);
			}
		}
		
	}

	public JobLauncher getJobLauncher() {
		return jobLauncher;
	}

	public void setJobLauncher(JobLauncher jobLauncher) {
		this.jobLauncher = jobLauncher;
	}
	
	public JobRepository getJobRepository() {
		return jobRepository;
	}

	public Job getJob() {
		return job;
	}

	public void setJob(Job job) {
		this.job = job;
	}
}
